package com.ruoyi.common.utils.ZipAnAra;

/**
 * 功能：
 *
 * @author：F_baisi
 * @create：2020/8/28 16:38
 * @version：2020 Version：1.0
 * @company：小牛科技 Created with IntelliJ IDEA
 */
import com.github.junrar.Archive;
import com.github.junrar.rarfile.FileHeader;
import org.apache.tools.zip.ZipEntry;
import org.apache.tools.zip.ZipFile;

import java.io.*;
import java.nio.charset.Charset;
import java.util.Enumeration;
import java.util.List;

public class UnZipAnRar {

	public static void unZip(File zipFile, String outDir) throws IOException {

		File outFileDir = new File(outDir);
		if (!outFileDir.getParentFile().exists())
		{
			outFileDir.getParentFile().mkdirs();
		}
		if (!outFileDir.exists())
		{
			outFileDir.mkdirs();
		}
		System.setProperty("sun.zip.encoding", System.getProperty("sun.jnu.encoding"));
//            zip = new ZipFile(zipFile, Charset.forName("UTF-8"));//防止中文目录，乱码
		String encoding = null;
		try {
			encoding = getEncoding(zipFile.getPath());
			ZipFile zip = new ZipFile(zipFile,encoding);
		for (Enumeration enumeration = zip.getEntries(); enumeration.hasMoreElements(); ) {
			ZipEntry entry = (ZipEntry) enumeration.nextElement();
			String zipEntryName = entry.getName();
			InputStream in = zip.getInputStream(entry);

			File fileDir = new File(outDir + zipEntryName);
			if (!fileDir.getParentFile().exists())
			{
				fileDir.getParentFile().mkdirs();
			}
			if (entry.isDirectory()) {      //处理压缩文件包含文件夹的情况

				if (!fileDir.exists())
				{
					fileDir.mkdirs();
				}
				continue;
			}

			File file = new File(outDir, zipEntryName);
			System.out.println("XXXXXXXXX:"+outDir+"YYYYYY"+zipEntryName);
			file.createNewFile();
			OutputStream out = new FileOutputStream(file);
			byte[] buff = new byte[1024];
			int len;
			while ((len = in.read(buff)) > 0) {
				out.write(buff, 0, len);
			}
			in.close();
			out.close();
		}
			zip.close();
		} catch (Exception e) {
			e.printStackTrace();
		}
	}

	public static void unRar(File rarFile, String outDir) throws Exception {
		File outFileDir = new File(outDir);
		if (!outFileDir.exists()) {
			boolean isMakDir = outFileDir.mkdirs();
			if (isMakDir) {
				System.out.println("创建压缩目录成功");
			}
		}
		Archive archive = new Archive(new FileInputStream(rarFile));
		FileHeader fileHeader = archive.nextFileHeader();
		while (fileHeader != null) {
			if (fileHeader.isDirectory()) {
				fileHeader = archive.nextFileHeader();
				continue;
			}
			File out = new File(outDir + fileHeader.getFileNameString());
			if (!out.exists()) {
				if (!out.getParentFile().exists()) {
					out.getParentFile().mkdirs();
				}
				out.createNewFile();
			}
			FileOutputStream os = new FileOutputStream(out);
			archive.extractFile(fileHeader, os);

			os.close();

			fileHeader = archive.nextFileHeader();
		}
		archive.close();
	}

	@SuppressWarnings("unchecked")
	private static String getEncoding(String path) throws Exception {
		String encoding = "GBK";
		net.lingala.zip4j.core.ZipFile zipFile = new net.lingala.zip4j.core.ZipFile(path);
		zipFile.setFileNameCharset(encoding);
		List<net.lingala.zip4j.model.FileHeader> list = zipFile.getFileHeaders();
		for (int i = 0; i < list.size(); i++) {
			net.lingala.zip4j.model.FileHeader fileHeader = list.get(i);
			String fileName = fileHeader.getFileName();
			if (isMessyCode(fileName)) {
				encoding = "UTF-8";
				break;
			}
		}
		return encoding;
	}


	private static boolean isMessyCode(String str) {
		for (int i = 0; i < str.length(); i++) {
			char c = str.charAt(i);
			// 当从Unicode编码向某个字符集转换时，如果在该字符集中没有对应的编码，则得到0x3f（即问号字符?）
			// 从其他字符集向Unicode编码转换时，如果这个二进制数在该字符集中没有标识任何的字符，则得到的结果是0xfffd
			if ((int) c == 0xfffd) {
				// 存在乱码
				return true;
			}
		}
		return false;
	}


}
